﻿#region Using namespaces

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Linq;
using System.Text;
using System.Threading;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Data;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Imaging;
using System.Windows.Navigation;
using System.Windows.Shapes;
using System.Windows.Threading;

using BOL.Apps.GeneNetworkBrowser.Windows;

#endregion

namespace BOL.Apps.GeneNetworkBrowser.Controls
{
    public partial class AnalysisExpander : Expander
    {
        #region Protected variables

        protected DispatcherTimer _timer;
        protected ManualResetEvent _busy;
        protected BackgroundWorker _worker;
        protected MainWindow _mw;

        #endregion

        #region Public properties

        //public object Content { get { return (object)GetValue(ContentProperty); } set { SetValue(ContentProperty, value); } }

        //public static readonly DependencyProperty ContentProperty = DependencyProperty.Register("Content", typeof(object), typeof(AnalysisExpander), new FrameworkPropertyMetadata(null, FrameworkPropertyMetadataOptions.AffectsRender | FrameworkPropertyMetadataOptions.AffectsParentMeasure));

        #endregion

        #region Constructor

        public AnalysisExpander()
        {
            DefaultStyleKeyProperty.OverrideMetadata(typeof(AnalysisExpander), new FrameworkPropertyMetadata(typeof(AnalysisExpander)));

            _timer = new DispatcherTimer();
            _busy = new ManualResetEvent(false);
            _mw = Application.Current.MainWindow as MainWindow;
        }

        #endregion

        #region Private methods

        private void Play(object sender, RoutedEventArgs e)
        {
            // create our background worker and support cancellation     
            _worker = new BackgroundWorker();
            _worker.WorkerReportsProgress = true;
            _worker.WorkerSupportsCancellation = true;
            _worker.DoWork += DoWork;
            _worker.RunWorkerCompleted += RunWorkerCompleted;
            _worker.ProgressChanged += ProgressChanged;

            //run the process then show the progress dialog     
            _worker.RunWorkerAsync();
        }

        private void Pause(object sender, RoutedEventArgs e)
        {
            ResumeWork();
        }

        private void Stop(object sender, RoutedEventArgs e)
        {
            CancelWorker();
        }

        #endregion

        #region Protected methods

        protected virtual void DoWork(object sender, DoWorkEventArgs args)
        {
            // create a Timer with a Normal Priority
            _timer = new DispatcherTimer();

            // set the Interval to 2 seconds
            _timer.Interval = TimeSpan.FromMilliseconds(2000);

            // set the callback to just show the time ticking away
            _timer.Tick += new EventHandler(delegate(object s, EventArgs a)
            {
                _mw.PrintMessage(string.Format("Timer ticked: {0}ms", Environment.TickCount));
            });

            // start the timer
            _timer.Start();
        }

        protected virtual void RunWorkerCompleted(object sender, RunWorkerCompletedEventArgs args)
        {
            if (args.Cancelled)
                _mw.PrintMessage("Cancelled.");
            else if (args.Error != null)
                _mw.PrintMessage("Exception thrown.");
            else
                _mw.PrintMessage("Completed.");
        }

        protected void ProgressChanged(object s, ProgressChangedEventArgs args)
        {
            //this._progressBar.Value = args.ProgressPercentage;
        }

        protected void ResumeWork()
        {
            _mw.PrintMessage("Resumed.");

            // start the worker if it isn't running 
            if (!_worker.IsBusy)
                _worker.RunWorkerAsync();

            // unblock the worker.
            _busy.Set();
        }

        protected void PauseWorker()
        {
            _mw.PrintMessage("Paused.");

            // block the worker 
            _busy.Reset();
        }

        protected void CancelWorker()
        {
            if (_worker.IsBusy)
            {
                // set CancellationPending property to true 
                _worker.CancelAsync();

                // unblock worker so it can see that 
                _busy.Set();
            }
        }

        #endregion
    }
}
